﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

using hotel.Win.BaseData;
using hotel.DAL;
using hotel.Common;
using hotel.Win.Common;
using hotel.Win.Query;

namespace hotel.Win.Subscribe
{
    /// <summary>
    /// 结帐退房
    /// </summary>
    public partial class jztfFrm : Form
    {
        hotelEntities _context;
        RZJL rzjlModel;
        string showMessage;
        List<XFJL> xfljs;//消费累计
        List<XFJL> zfljs;//支付累计
        List<string> rzjlIds;//所有入住纪录ID
        bool isHeDan;//是否是合单，即关联房
        #region 公有属性       
        /// <summary>
        /// 所有登记房间
        /// </summary>
        public List<string> RoomIds { get; private set; }
        #endregion

        public jztfFrm(string rzzh)
        {
            InitializeComponent();
            showMessage = "";
            _context = MyDataContext.GetDataContext;           
            rzjlModel = _context.RZJL.First(p => p.ID == rzzh);
            lbzh.Text = rzzh;            
            lbfh.Text = rzjlModel.ROOM.ID;            
            lbfl.Text = rzjlModel.ROOM.ROOM_TYPE.JC;
            lbfj.Text = rzjlModel.SJFJ.ToString();
            lbddrq.Text = rzjlModel.DDRQ.Value.Date.ToString("yyyy-MM-dd");
            lbldrq.Text = rzjlModel.LDRQ.Value.Date.ToString("yyyy-MM-dd");
            lbyzts.Text = (DateTime.Now.Date - rzjlModel.DDRQ.Value.Date).Days.ToString();
            btnrmbjz.Enabled = true;
            BindFJ();
            InitGrid();
            this.rbtnmz.CheckedChanged += new System.EventHandler(this.jsfzRbtn_CheckedChanged);
            this.rbtnbtz.CheckedChanged += new System.EventHandler(this.jsfzRbtn_CheckedChanged);
            this.rbtnqz.CheckedChanged += new System.EventHandler(this.jsfzRbtn_CheckedChanged);
        }

        /// <summary>
        /// 显示超时提醒
        /// </summary>
        private void ShowChaoShiTiXing()
        {
            var xtcs = XTCSModel.GetXTCS;
            var btdate = Convert.ToDateTime(DateTime.Now.Date.ToString("yyyy-MM-dd ") + xtcs.JBTFZ_SJ);
            var ytdate = Convert.ToDateTime(DateTime.Now.Date.ToString("yyyy-MM-dd ") + xtcs.JYTFZ_SJ);
            //var lastYs = _context.YSJL.Max(p => p.YYRQ).Value;//最后一次夜审时间
            
            //decimal jsfz = 0;
            //夜审之后来的，当天退房
            //if (rzjlModel.DDRQ.Value > lastYs)
            //{
            //    jsfz = rzjlModel.SJFJ.Value;
            //    msg = "夜审过后入住，加收全天房租";
            //}
            rbtnmz.Checked = true;
            //钟点房特殊计算
            if (rzjlModel.XYJG_MC == RoomStstusCnName.ZhongDian)
            {
                groupBoxjsfz.Enabled = false;
                txtjsfz.Value = 0;
                var hour = Math.Ceiling((DateTime.Now - rzjlModel.LDRQ.Value).TotalHours);
                if (hour > 0)
                {
                    //协议房价配置
                    var xyData = _context.RoomTypePrice.FirstOrDefault(p => p.ROOM_TYPE_ID == rzjlModel.ROOM.ROOM_TYPE_ID && p.XYMC== rzjlModel.XYJG_MC);
                   if (xyData!=null)
                   {
                      txtjsfz.Value = Math.Round(Convert.ToDecimal(hour) * xyData.ZDF_JS,0);
                      MessageBox.Show("钟点房入住超时，加收房价" + txtjsfz.Value.ToString());
                   }
                }
            }
            else
            {
                groupBoxjsfz.Enabled = true;
                //前一天是否过房租
                var yyrq = Convert.ToDateTime(XTCSModel.GetXTCS.YYRQ).AddDays(-1);
                bool isDayFz = _context.XFJL.Count(p => p.RZJL_ID == rzjlModel.ID && p.XFXM_MC == "房租" && p.CJRQ > yyrq) > 0;
                if (!isDayFz)
                {
                    rbtnqz.Checked = true;//全租
                }
                else
                {
                    //加收
                    if (DateTime.Now >= btdate && DateTime.Now < ytdate)
                    {
                        showMessage = "客人退房时间已经超过" + xtcs.JBTFZ_SJ + "点,自动加收半天房租!";
                        //jsfz = Convert.ToInt32(rzjlModel.SJFJ.Value / 2);
                        rbtnbtz.Checked = true;
                    }
                    else if (DateTime.Now >= ytdate)
                    {
                        showMessage = "客人退房时间已经超过" + xtcs.JYTFZ_SJ + "点,自动加收全天房租!";
                        //jsfz = rzjlModel.SJFJ.Value;
                        rbtnqz.Checked = true;
                    }
                }

                jsfzRbtn_CheckedChanged(null, null);
            }
           
           // txtjsfz.Value = jsfz* RoomIds.Count;
        }

        private void InitGrid()
        {
           
            xfljs = new List<XFJL>();
            zfljs = new List<XFJL>();
            isHeDan = false;
            IEnumerable<XFJL> qry;
            
            gboxZhclq.Enabled = true;
            gboxdy.Enabled = false;
            //考虑合并帐单的情况
            if (string.IsNullOrEmpty(rzjlModel.F_ID))
            {                
                //一般或父单
                qry = _context.XFJL.Where(p => p.RZJL.ID == rzjlModel.ID);
                xfljs.AddRange(qry.Where(p => p.XFXM_MC != "押金"));
                zfljs.AddRange(qry.Where(p => p.XFXM_MC == "押金"));
                //如果有子帐单
                qry = from r in _context.RZJL
                      join x in _context.XFJL on r.ID equals x.RZJL.ID
                      where r.F_ID == rzjlModel.ID
                      select x;
                if (qry.Count() > 0)
                {
                    xfljs.AddRange(qry.Where(p => p.XFXM_MC != "押金"));
                    zfljs.AddRange(qry.Where(p => p.XFXM_MC == "押金"));
                    isHeDan = true;
                  
                }
                
            }
            else
            {
                isHeDan = true;
                //子单
                qry = from r in _context.RZJL
                      join x in _context.XFJL on r.ID equals x.RZJL.ID
                      where r.F_ID == rzjlModel.F_ID
                      select x;
                if (qry.Count() > 0)
                {
                    xfljs.AddRange(qry.Where(p => p.XFXM_MC != "押金"));
                    zfljs.AddRange(qry.Where(p => p.XFXM_MC == "押金"));
                }
                //自身
                qry = _context.XFJL.Where(p => p.RZJL.ID == rzjlModel.F_ID);
                xfljs.AddRange(qry.Where(p => p.XFXM_MC != "押金"));
                zfljs.AddRange(qry.Where(p => p.XFXM_MC == "押金"));
                
            }
            
            BindGrid();
            //帐务信息            
            //全部挂账，可能小于0
            txtljxf.Value = (decimal)xfljs.Sum(p => p.JE);
            txtysje.Value = (decimal)zfljs.Sum(p => p.YJ);
            ShowChaoShiTiXing();
            txtkrzf.Value =txtysje.Value - txtljxf.Value- txtjsfz.Value;            
        }

        private void BindGrid()
        {
            //消费累计           
            gridxf.AutoGenerateColumns = false;
            gridxf.DataSource = (from q in xfljs
                                 orderby q.ROOM.ID,q.CJRQ
                                select new
                                {
                                    ROOM_ID = q.ROOM.ID,
                                    q.CJRQ,
                                    q.CJRY,
                                    q.JE,
                                    q.SL,
                                    q.DJ,
                                    q.XFXM_MC,
                                    q.YJ,
                                    q.ZFFS,
                                    q.BZSM,
                                    q.ID
                                }).ToList();
            //支付累计           
            gridzf.AutoGenerateColumns = false;
            gridzf.DataSource = (from q in zfljs
                                 orderby q.ROOM.ID,q.CJRQ
                                select new
                                {
                                    ROOM_ID = q.ROOM.ID,
                                    q.CJRQ,
                                    q.CJRY,
                                    q.JE,
                                    q.SL,
                                    q.DJ,
                                    q.XFXM_MC,
                                    q.YJ,
                                    q.ZFFS,
                                    q.ID
                                }).ToList();
        }

        /// <summary>
        /// 绑定房间
        /// </summary>
        private void BindFJ()
        {
            treefj.Nodes.Clear();
            rzjlIds = new List<string>();
            List<string> rooms = new List<string>();
          
            rooms.Add(rzjlModel.ROOM_ID);
            rzjlIds.Add(rzjlModel.ID);
            if (string.IsNullOrEmpty(rzjlModel.F_ID))
            {
                //找子房间
                foreach (var item in _context.RZJL.Where(p => p.F_ID == rzjlModel.ID))
                {
                    rooms.Add(item.ROOM_ID);
                    rzjlIds.Add(item.ID);
                }
            }
            else
            {
                foreach (var item in _context.RZJL.Where(p => p.F_ID == rzjlModel.F_ID && p.ID != rzjlModel.ID))
                {
                    rooms.Add(item.ROOM_ID);
                    rzjlIds.Add(item.ID);
                }
                foreach (var item in _context.RZJL.Where(p => p.ID == rzjlModel.F_ID))
                {
                    rooms.Add(item.ROOM_ID);
                    rzjlIds.Add(item.ID);
                }
            }

             RoomIds = new List<string>();
            foreach (var item in rooms)
            {
                treefj.Nodes.Add(item);
                RoomIds.Add(item);
            }
            if (treefj.Nodes.Count > 1)
                treefj.Nodes.Insert(0,hotel.Common.SysConsts.AllItem);
            var fksl = (from t in _context.FKSYXX
                        where rzjlIds.Any(c => c == t.RZJL_ID) && t.SFGH == "否"
                     select t).GroupBy(p => p.KH).Count();
            lbfksl.Text = fksl.ToString();
        }

        private void btnrmbjz_Click(object sender, EventArgs e)
        {            
            if (txtkrzf.Value < 0)
            {
                MessageBox.Show("客人的预付押金不足，请增加！");
                return;
            }
            if (MessageBox.Show("你确定结账退房吗？", "结账退房", MessageBoxButtons.OKCancel) != System.Windows.Forms.DialogResult.OK)
                return;
            //处理剩余的押金
            /*if (txtkrzf.Value > 0)
            {
                //JZTR结账退入
                var xfxmModel = _context.XFXM.First(p => p.DM == "JZTR");
                var xfjlModel = XFJL.CreateXFJL(0, 0, rzjlModel.ID, rzjlModel.ROOM_ID, xfxmModel.ID);
                xfjlModel.CJRQ = DateTime.Now;
                xfjlModel.CJRY = UserLoginInfo.FullName;
                xfjlModel.DJ = 0;
                xfjlModel.SL = 1;
                xfjlModel.JE = 0;
                xfjlModel.YJ = -(int)txtkrzf.Value;
                xfjlModel.XFXM_MC = xfxmModel.MC;
                _context.AddToXFJL(xfjlModel);
                _context.SaveChanges();
            }
            */
            //@rzid 如果是合并的帐单，则为父的RZJL.ID
            //帐单合并只支持一层
            string rzid = string.IsNullOrEmpty(rzjlModel.F_ID) ? rzjlModel.ID : rzjlModel.F_ID;
            _context.RZJL_JZTF_PROC(rzid, UserLoginInfo.FullName,"是",txtkrzf.Value,txtjsfz.Value);
            #region 日志纪录
            CcrzInfo logInfo = null;
            logInfo = new CcrzInfo();
            logInfo.Abstract = LogAbstractEnum.结账退房;
            logInfo.Type = LogTypeEnum.涉及金额;
            logInfo.RoomId = rzjlModel.ROOM_ID;
            logInfo.Rzid = rzjlModel.ID;
            logInfo.Message ="房号[" + lbfh.Text + "]"+ ",消费总额=" + (txtljxf.Value + txtjsfz.Value).ToString() +
                ",押金总额=" + txtysje.Value.ToString();
            if (txtjsfz.Value > 0)
                logInfo.Message += ",加收房租=" + txtjsfz.Value.ToString();
            logInfo.Save();
            #endregion
            MessageBox.Show("结帐成功，请打印相关单据");
            btnbjztf.Enabled = false;
            gboxZhclq.Enabled = false;
            gboxdy.Enabled = true;
            btnrmbjz.Enabled = false;
        }
        //签单结账
        private void btnqtjz_Click(object sender, EventArgs e)
        {
            // + txtjsfz.Value ,加收的房租不能用于挂账
            var frm = new xydwGzMaintain(rzjlModel, _context, txtljxf.Value);
            if (frm.ShowDialog() != DialogResult.OK)
                return;

            string rzid = string.IsNullOrEmpty(rzjlModel.F_ID) ? rzjlModel.ID : rzjlModel.F_ID;
            _context.PROC_JZTF_QD(rzid, UserLoginInfo.FullName, frm.SelectedXYDW.XYDM, frm.SelectedXYDW.DWMC, frm.Gzje,frm.Bzsm,frm.Xgdm);
            InitGrid();//刷新页面
            MessageBox.Show("挂账成功");            
            InitGrid();            
            #region 日志纪录
            CcrzInfo logInfo = null;
            logInfo = new CcrzInfo();
            logInfo.Abstract = LogAbstractEnum.单位挂账退房;
            logInfo.Type = LogTypeEnum.涉及金额;
            logInfo.RoomId = rzjlModel.ROOM_ID;
            logInfo.Rzid = rzjlModel.ID;
            logInfo.Message = "房号[" + lbfh.Text + "]" +
                 ",挂账总额=" + frm.Gzje.ToString();
            if (frm.Xgdm.Length > 0 || frm.Bzsm.Length > 0)
                logInfo.Message += "," + frm.Xgdm + "," + frm.Bzsm;
            logInfo.Save();
            #endregion
        }

        /// <summary>
        /// 转其他房退房，包括押金
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btnzqtf_Click(object sender, EventArgs e)
        {
            var frm = new fjFind("费用转单");
            if (frm.ShowDialog() != DialogResult.OK)
                return;
            var rzzh = frm.SelectedRZJL.ID;
            var mbrzjlModel = _context.RZJL.FirstOrDefault(p => p.ID == rzzh); //目标入住记录
            if (mbrzjlModel == null)
                return;
            var xfjls = from q in _context.XFJL
                        where q.RZJL.ID == rzjlModel.ID
                        select q;            
            foreach (var item in xfjls)
            {
                item.ROOM = mbrzjlModel.ROOM;
                item.RZJL = mbrzjlModel;
                item.BZSM += "从" + rzjlModel.ROOM_ID + "房间转入的结帐项目";
            }
            rzjlModel.BZSM += "消费转账到" + mbrzjlModel.ROOM_ID;
            _context.SaveChanges();
            #region 日志纪录
            CcrzInfo logInfo = null;
            logInfo = new CcrzInfo();
            logInfo.Abstract = LogAbstractEnum.消费转单;
            logInfo.Type = LogTypeEnum.涉及金额;
            logInfo.RoomId = mbrzjlModel.ROOM_ID;
            logInfo.Rzid = mbrzjlModel.ID;
            logInfo.Message = "房号[" + lbfh.Text + "]" + ",消费总额=" + txtljxf.Value.ToString() +
                ",押金总额=" + txtysje.Value.ToString();
            logInfo.Save();
            #endregion
            txtljxf.Value = 0;
            txtysje.Value = 0;            
            txtkrzf.Value = 0;
            if (MessageBox.Show("消费转帐成功！是否将" + rzjlModel.ROOM.ID + "房间退房！", "提示消息", MessageBoxButtons.OKCancel) != DialogResult.OK)
                return;
            btnrmbjz_Click(btnrmbjz, null);
        }

        private void treefj_AfterSelect(object sender, TreeViewEventArgs e)
        {
            if (hotel.Common.SysConsts.AllItem == e.Node.Text)
            {
                BindGrid();
            }
            else
            {
                //消费累计           
                gridxf.AutoGenerateColumns = false;
                gridxf.DataSource = (from q in xfljs
                                    where q.ROOM.ID == e.Node.Text
                                     orderby q.ROOM.ID,q.CJRQ
                                    select new
                                    {
                                        ROOM_ID = q.ROOM.ID,
                                        q.CJRQ,
                                        q.CJRY,
                                        q.JE,
                                        q.SL,
                                        q.DJ,
                                        q.XFXM_MC,
                                        q.YJ,
                                        q.ZFFS,
                                        q.ID
                                    }).ToList();
                //支付累计           
                gridzf.AutoGenerateColumns = false;
                gridzf.DataSource = (from q in zfljs
                                    where q.ROOM.ID == e.Node.Text
                                     orderby q.ROOM.ID,q.CJRQ
                                    select new
                                    {
                                        ROOM_ID = q.ROOM.ID,
                                        q.CJRQ,
                                        q.CJRY,
                                        q.JE,
                                        q.SL,
                                        q.DJ,
                                        q.XFXM_MC,
                                        q.YJ,
                                        q.ZFFS,
                                        q.ID
                                    }).ToList();
            }
        }

        private void jztfFrm_Shown(object sender, EventArgs e)
        {
            if (lbfh.Text == SysConsts.Room9999)
            {
                MessageBox.Show(lbfh.Text + "非住房，不能结帐");
                this.Close();
            }
            if (showMessage != "")
                MessageBox.Show(showMessage);
            txtkrzf.Focus();
        }

        private void btndyzd_Click(object sender, EventArgs e)
        {
           //Point formPoint = Control.MousePosition; //鼠标位置           
           // contextMenuStrip1.Show(formPoint);
            CcrzInfo logInfo = null;
            logInfo = new CcrzInfo();
            logInfo.Abstract = LogAbstractEnum.打印;
            logInfo.Type = LogTypeEnum.一般操作;
            logInfo.Message = "结账退房汇总表，房号[" + lbfh.Text + "]" + ",消费总额=" + txtljxf.Value.ToString() +
                ",押金总额=" + txtysje.Value.ToString();
            var rzid = string.IsNullOrEmpty(rzjlModel.F_ID) ? rzjlModel.ID : rzjlModel.F_ID;
            logInfo.Rzid= rzid;
            Report.ReportEntry.ShowXiaoFeiSumBill(XTCSModel.GetXTCS.JDMC, rzid, logInfo);
        }
        private void btnxfmxb_Click(object sender, EventArgs e)
        {
            CcrzInfo logInfo = null;
            logInfo = new CcrzInfo();            
            logInfo.Abstract = LogAbstractEnum.打印;
            logInfo.Type = LogTypeEnum.一般操作;
            logInfo.Message = "结账退房明细表";
            var rzid = string.IsNullOrEmpty(rzjlModel.F_ID) ? rzjlModel.ID : rzjlModel.F_ID;
            logInfo.Rzid = rzid;
            hotel.Win.Report.ReportEntry.ShowXiaoFeiMingXiBill(XTCSModel.GetXTCS.JDMC, rzid, isHeDan, logInfo);
        }

        private void toolStripMenuItem2_Click(object sender, EventArgs e)
        {
            
        }

        private void btnxfrd_Click(object sender, EventArgs e)
        {
            var frm = new krfyMaintain(lbzh.Text);
            if (frm.ShowDialog() == System.Windows.Forms.DialogResult.OK)
            {
                InitGrid();
            }
        }

        private void btnxdyj_Click(object sender, EventArgs e)
        {
            var frm = new yjclFrm(lbzh.Text);
            if (frm.ShowDialog() == System.Windows.Forms.DialogResult.OK)
            {
                InitGrid();
            }
        }

        private void txtkrzf_DoubleClick(object sender, EventArgs e)
        {
            MessageBox.Show(txtkrzf.Value.ToString());
        }
        //加房租
        private void jsfzRbtn_CheckedChanged(object sender, EventArgs e)
        {
            if (rbtnqz.Checked)
                txtjsfz.Value = rzjlModel.SJFJ.Value * RoomIds.Count;
            else if (rbtnbtz.Checked)
                txtjsfz.Value = (int)rzjlModel.SJFJ.Value * RoomIds.Count / 2;
            else if (rbtnmz.Checked)
                txtjsfz.Value = 0;
 
            txtkrzf.Value = txtysje.Value - txtljxf.Value - txtjsfz.Value;
            if (txtjsfz.Value > 0)
                txtjsfz.BackColor = txtkrzf.BackColor;
        }

        private void jztfFrm_FormClosed(object sender, FormClosedEventArgs e)
        {
            _context.Dispose();
        }
        //不结账退房
        private void btnbjztf_Click(object sender, EventArgs e)
        {
            var str = "";
            //运行押金小于0结账
            if (txtkrzf.Value < 0)
                str = "【注意】客人的预付押金不足,押金：" + txtkrzf.Value.ToString() + "\n";

            if (MessageBox.Show(str + "你确定不结账退房吗？", "不结账退房", MessageBoxButtons.OKCancel) != System.Windows.Forms.DialogResult.OK)
                return;
            string rzid = string.IsNullOrEmpty(rzjlModel.F_ID) ? rzjlModel.ID : rzjlModel.F_ID;
            _context.RZJL_JZTF_PROC(rzid, UserLoginInfo.FullName, "否", 0, txtjsfz.Value); 
            MessageBox.Show("不结帐退房，成功");
            btnbjztf.Enabled = false;
            btnrmbjz.Enabled = false;
            gboxZhclq.Enabled = false;
            gboxdy.Enabled = true;
            btnrmbjz.Enabled = false;
            #region 日志纪录
            var logInfo = new CcrzInfo();
            logInfo.Abstract = LogAbstractEnum.不结账退房;
            logInfo.RoomId = rzjlModel.ROOM_ID;
            logInfo.Rzid = rzid;
            logInfo.Message = "押金:" + txtysje.Value.ToString() 
                + ",消费:" + (txtljxf.Value + txtjsfz.Value ).ToString()
                + ",加收房租:" + txtjsfz.Value.ToString();
            logInfo.Save();
            #endregion
        }

        private void lbfksl_Click(object sender, EventArgs e)
        {
            var frm = new FangKaView(rzjlModel.ID);
            frm.BindDatas(rzjlIds);
            frm.ShowDialog();
        }         
    }
}
